#include "MephistoCAM.h"

int main( int argc, char *argv[] ){

    struct timeval start;
	struct timeval end;
	
	gettimeofday(&start, NULL);

/**** handle option parameters ****/
	int opt;
	opterr = 1;

	int n_row 			= 4666;	// default
	int n_col 			= 1248;	// default
	int fast_read_opt	= 0;
	int n_bytes			= 4;	// default 32bits float
	int is_master       = 0;

	char fout_name[1024]= "tmp.bin";
	
	// int fname_set 			= -1;
	// int n_row_set 			= -1;
	// int n_col_set			= -1;
	// int fast_read_opt_set	= -1;

	while( (opt=getopt(argc,argv,"r:c:f:o:b:m:")) != -1 ){
		switch(opt){
			case 'm':
			    is_master = atoi(optarg);
			    printf("(%s)> is_master = %d\n", __FUNCTION__, is_master);
			    break;
			case 'r':
				n_row = atoi(optarg);
				printf("(%s)> Num. of vertical transfers: %d\n", __FUNCTION__, n_row);
				break;
			case 'c':
				n_col = atoi(optarg);
				printf("(%s)> Num. of horizontal transfers: %d\n", __FUNCTION__, n_col);
				break;
			case 'f':
				fast_read_opt = atoi(optarg);
				break;
			case 'o':
				sprintf(fout_name, "%s", optarg);
				printf("(%s)> data will be saved into: %s\n", __FUNCTION__, fout_name);
				break;
			case 'b':
				n_bytes = atoi(optarg);
				printf("(%s)> date format %d bytes (2 bytes: 16bits unsigned; 4 bytes: 32bits float).\n", __FUNCTION__, n_bytes);
				break;
			default:
				break;
		}
	}
	
	printf("(%s)> is_master = %d\n", __FUNCTION__, is_master);
	
/*	exit(0);*/

	// if( fname_set == -1 ){
	// 	sprintf(fout_name, "tmp.fits");
	// }

/**** memery map ****/

	int fd_gpio = open("/dev/mem", O_RDWR | O_SYNC);

	// ADDR_GPIO_OUT --> 0x41220000
	uint32_t *gpio_reg_ctrl = mmap(NULL, 4, PROT_READ | PROT_WRITE, MAP_SHARED, fd_gpio, ADDR_GPIO_OUT);

	// ADDR_GPIO_IN  --> 0x41210000
	uint32_t *gpio_reg_status = mmap(NULL, 4, PROT_READ | PROT_WRITE, MAP_SHARED, fd_gpio, ADDR_GPIO_IN);

	// ADDR_PL_PS_DDR_CNT --> 0x41210008
	// uint32_t *gpio_reg_pl_ps_ddr_cnt = mmap(NULL, 10, PROT_READ | PROT_WRITE, MAP_SHARED, fd_gpio, ADDR_PL_PS_DDR_CNT);
	uint32_t *gpio_reg_pl_ps_ddr_cnt = gpio_reg_status + 2;

/*	gettimeofday(&end, NULL);*/
/*    printf("==> Normal readout used time: %g s\n", time_diff(&start, &end));*/

    
/**** call ccd_exposure ****/
/*    gettimeofday(&start, NULL);*/

	ccd_readout( gpio_reg_ctrl, 
                 gpio_reg_status, 
                 gpio_reg_pl_ps_ddr_cnt, 
                 n_row,
                 n_col,
				 n_bytes,
                 fast_read_opt,
                 fout_name,
                 is_master );

	munmap(gpio_reg_ctrl,10);
	munmap(gpio_reg_status,10);
	munmap(gpio_reg_pl_ps_ddr_cnt,10);
	close(fd_gpio);

	gettimeofday(&end, NULL);
    printf("==> Normal readout used time: %g s\n", time_diff(&start, &end));
    
/*    sleep(30);*/

	return 0;
}
